package com.lbd.gulimall.product.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.TypeReference;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.lbd.common.to.SkuHasStockVo;
import com.lbd.common.utils.R;
import com.lbd.gulimall.product.entity.*;
import com.lbd.gulimall.product.feign.WareFeignService;
import com.lbd.gulimall.product.service.*;
import com.lbd.gulimall.product.vo.item.ItemBaseAttr;
import com.lbd.gulimall.product.vo.item.ItemSaleAttr;
import com.lbd.gulimall.product.vo.item.SkuItemVO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Arrays;
import java.util.List;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.stream.Collectors;

/**
 * @Author: linbd
 * @Description:
 * @Date: 2023/3/10 20:00
 */
@Slf4j
@Service
public class ItemServiceImpl implements ItemService {
    @Autowired
    private SkuInfoService skuInfoService;
    @Autowired
    private SkuImagesService skuImagesService;
    @Autowired
    private SpuInfoDescService spuInfoDescService;
    @Autowired
    private WareFeignService wareFeignService;
    @Autowired
    private ProductAttrValueService productAttrValueService;
    @Autowired
    private SkuSaleAttrValueService skuSaleAttrValueService;
    @Autowired
    private SpuInfoService spuInfoService;
    @Autowired
    private ThreadPoolExecutor threadPoolExecutor;

    @Override
    public SkuItemVO getSkuItem(Long skuId) throws ExecutionException, InterruptedException {
        SkuItemVO skuItemVO = new SkuItemVO();
        //1. sku基本信息  pms_sku_info
        CompletableFuture<Long> skuInfoFuture = CompletableFuture.supplyAsync(() -> {
            SkuInfoEntity skuInfo = skuInfoService.getById(skuId);
            Long spuId = skuInfo.getSpuId();
            skuItemVO.setSkuInfo(skuInfo);
            return spuId;
        }, threadPoolExecutor);

        //2. sku图片信息 pms_sku_images  （多张图片）
        CompletableFuture<Void> skuImagesFuture = CompletableFuture.runAsync(() -> {
            List<SkuImagesEntity> skuImages = skuImagesService.list(new QueryWrapper<SkuImagesEntity>().eq("sku_id", skuId));
            skuItemVO.setSkuImages(skuImages);
        }, threadPoolExecutor);

        //6. 是否有货  默认有货，如果调用库存接口失败，也默认有货
        CompletableFuture<Void> hasStockFuture = CompletableFuture.runAsync(() -> {
            Integer hasStock = 1;
            R r = wareFeignService.hasStock(Arrays.asList(skuId));
            if (r.getCode() == 0) {
                List<SkuHasStockVo> skuHasStockVos = r.getData(new TypeReference<List<SkuHasStockVo>>() {
                });
                hasStock = skuHasStockVos.get(0).getHasStock() ? 1 : 0;

            }
            skuItemVO.setHasStock(hasStock);
        }, threadPoolExecutor);

        //3,4,5需要等待1的结果，然后并行查询
        //3. spu销售属性组合 （当前sku所属spu下的其他sku信息）
        CompletableFuture<Void> itemSaleAttrsFuture = skuInfoFuture.thenAcceptAsync(spuId -> {
            List<ItemSaleAttr> itemSaleAttrs = skuSaleAttrValueService.getSaleAttrs(spuId);
            skuItemVO.setItemSaleAttrs(itemSaleAttrs);
        }, threadPoolExecutor);

        //4. spu介绍 spu_info_desc
        CompletableFuture<Void> spuInfoDescFuture = skuInfoFuture.thenAcceptAsync(spuId -> {
            SpuInfoDescEntity spuInfoDesc = spuInfoDescService.getById(spuId);
            skuItemVO.setSpuInfoDesc(spuInfoDesc);
        }, threadPoolExecutor);

        //5. spu规格参数（基本属性）信息
        CompletableFuture<Void> itemBaseAttrsFuture = skuInfoFuture.thenAcceptAsync(spuId -> {
            SpuInfoEntity spuInfoEntity = spuInfoService.getById(spuId);
            List<ItemBaseAttr> itemBaseAttrs = productAttrValueService.getBaseAttrs(spuId, spuInfoEntity.getCatalogId());
            skuItemVO.setItemBaseAttrs(itemBaseAttrs);
        }, threadPoolExecutor);

        CompletableFuture.allOf(itemSaleAttrsFuture, spuInfoDescFuture, itemBaseAttrsFuture, skuImagesFuture, hasStockFuture).get();
        log.info("skuId=【{}】的详情信息【{}】", skuId, JSON.toJSONString(skuItemVO));
        return skuItemVO;
    }
}
